using System;
using System.Reflection;

using NUnit.Framework;

using WCSFContrib.Extensions.EventBroker;

namespace WCSFContrib.Extensions.Tests.EventBroker
{
	[TestFixture]
	public class MemberReferenceTests
	{
		private MemberInfo memberInfo = typeof(MemberReferenceTests).GetMethod("SetUp");
		private MemberReference<MemberInfo> memberReference;
		private string expectedTopic = "foo";

		[SetUp]
		public void SetUp()
		{
			memberReference = new MemberReference<MemberInfo>(expectedTopic, memberInfo);
		}

		[Test]
		[ExpectedException(typeof(ArgumentNullException))]
		public void NullTopicFails()
		{
			new MemberReference<MemberInfo>(null, memberInfo);
		}

		[Test]
		[ExpectedException(typeof(ArgumentException))]
		public void EmptyTopicFails()
		{
			new MemberReference<MemberInfo>("", memberInfo);
		}

		[Test]
		[ExpectedException(typeof(ArgumentNullException))]
		public void NullInfoFails()
		{
			new MemberReference<MemberInfo>(expectedTopic, null);
		}

		[Test]
		public void PropertyTest()
		{
			Assert.AreEqual(expectedTopic, memberReference.Topic);
			Assert.AreEqual(memberInfo, memberReference.Info);
			Assert.AreEqual(GetType(), memberReference.DeclaringType);
		}

		[Test]
		public void Equals()
		{
			MemberReference<MemberInfo> otherMemerReference = new MemberReference<MemberInfo>(expectedTopic, memberInfo);

			bool result = memberReference.Equals(otherMemerReference);

			Assert.IsTrue(result);
		}

		[Test]
		public void TopicNotEquals()
		{
			MemberReference<MemberInfo> otherMemerReference = new MemberReference<MemberInfo>("another topic", memberInfo);

			bool result = memberReference.Equals(otherMemerReference);

			Assert.IsFalse(result);
		}

		[Test]
		public void MemberInfoNotEquals()
		{
			MemberInfo otherMemberInfo = GetType().GetMethod("MemberInfoNotEquals");
			MemberReference<MemberInfo> otherMemerReference = new MemberReference<MemberInfo>(expectedTopic, otherMemberInfo);

			bool result = memberReference.Equals(otherMemerReference);

			Assert.IsFalse(result);
		}

		[Test]
		public void GetHashCodeValue()
		{
			int expectedHashCode = memberReference.Topic.GetHashCode() ^ memberReference.Info.GetHashCode();

			int result = memberReference.GetHashCode();

			Assert.AreEqual(expectedHashCode, result);
		}
	}
}